/*
 * Copyright (C) 2021 Huawei Device Co., Ltd.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.andremion.louvre.home;

import com.andremion.louvre.CheckRadioView;
import com.andremion.louvre.ResourceTable;
import com.bumptech.glide.Glide;

import ohos.agp.components.BaseItemProvider;
import ohos.agp.components.Component;
import ohos.agp.components.ComponentContainer;
import ohos.agp.components.Text;
import ohos.agp.components.LayoutScatter;
import ohos.agp.components.AttrHelper;
import ohos.agp.components.Image;
import ohos.app.Context;
import ohos.utils.net.Uri;

import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;

/**
 * GalleryFragmentAdapter
 */
public class GalleryFragmentAdapter extends BaseItemProvider {
    static int mMaxSelection = 0;
    private static final float SELECTED_SCALE = .8f;
    private static final float UNSELECTED_SCALE = 1f;
    private List<Uri> mImages;
    private Context mContext;
    private GalleryAdapter.Callbacks mCallbacks;

    private List<Uri> selection = new ArrayList<>();

    public GalleryFragmentAdapter(Context mContext, GalleryAdapter.Callbacks mCallbacks, List<Uri> mImages) {
        this.mContext = mContext;
        this.mImages = mImages;
        this.mCallbacks = mCallbacks;
    }

    public List<Uri> getSelection() {
        return selection;
    }

    public void setSelection(List<Uri> selection) {
        this.selection = selection;
    }

    void setMaxSelection(int mMaxSelection) {
        this.mMaxSelection = mMaxSelection;
    }

    @Override
    public int getCount() {
        return mImages.size();
    }

    @Override
    public Object getItem(int i) {
        return null;
    }

    @Override
    public long getItemId(int i) {
        return i;
    }

    @Override
    public Component getComponent(int i, Component component, ComponentContainer componentContainer) {
        Image mImageView;
        CheckRadioView radioCheck;
        Text mTextView;
        int screenWidth = AttrHelper.fp2px(componentContainer.getContext()
                .getResourceManager().getDeviceCapability().width, componentContainer.getContext());
        int w = screenWidth / 2;

        Component v = LayoutScatter.getInstance(componentContainer.getContext())
                .parse(ResourceTable.Layout_list_item_gallery_media, componentContainer, false);
        ComponentContainer.LayoutConfig layoutConfig = new ComponentContainer.LayoutConfig(w, w);
        v.setLayoutConfig(layoutConfig);
        mImageView = (Image) v.findComponentById(ResourceTable.Id_image);
        radioCheck = (CheckRadioView) v.findComponentById(ResourceTable.Id_radioCheck);
        mImageView.setLayoutConfig(layoutConfig);
        radioCheck.setClickedListener(new Component.ClickedListener() {
            @Override
            public void onClick(Component component) {
                boolean selectionChanged = handleChangeSelection(i);
                if (selectionChanged) {
                    notifyDataSetItemChanged(i);
                    radioCheck.setChecked(true);
                } else {
                    radioCheck.setChecked(false);
                }
                if (mCallbacks != null) {
                    if (selectionChanged) {
                        mCallbacks.onSelectionUpdated(selection.size());
                    } else {
                        mCallbacks.onMaxSelectionReached();
                    }
                }
            }
        });

        boolean selected = isSelected(i);
        if (selected) {
            mImageView.setScaleX(SELECTED_SCALE);
            mImageView.setScaleY(SELECTED_SCALE);
        } else {
            mImageView.setScaleX(UNSELECTED_SCALE);
            mImageView.setScaleY(UNSELECTED_SCALE);
        }
        radioCheck.setChecked(selected);
        Glide.with(componentContainer.getContext())                             //配置上下文
                .load(Uri.parse(mImages.get(i).toString()))        //设置图片路径(fix #8,文件名包含%符号 无法识别和显示)
                .into(mImageView);
        v.setClickedListener(new Component.ClickedListener() {
            @Override
            public void onClick(Component component) {
                if (mCallbacks != null) {
                    mCallbacks.onMediaClick(mImageView, radioCheck, 0, i);
                }
            }
        });
        return v;
    }

    private boolean handleChangeSelection(int position) {
        Uri data = mImages.get(position);
        if (!isSelected(position)) {
            if (selection.size() >= mMaxSelection) {
                return false;
            }
            selection.add(data);
        } else {
            selection.remove(data);
        }
        return true;
    }

    private boolean isSelected(int position) {
        Uri data = mImages.get(position);
        return selection.contains(data);
    }

    void selectAll() {
        if (mImages == null) {
            return;
        }
        List<Uri> selectionToAdd = new LinkedList<>();
        for (int position = 0; position < mImages.size(); position++) {
            if (!isSelected(position)) {
                Uri data = mImages.get(position);
                selectionToAdd.add(data);
            }
        }
        if (selection.size() + selectionToAdd.size() > mMaxSelection) {
            if (mCallbacks != null) {
                mCallbacks.onWillExceedMaxSelection();
            }
        } else {
            selection.addAll(selectionToAdd);
            mCallbacks.onSelectionUpdated(selection.size());
            GalleryFragmentAdapter.this.notifyDataChanged();
        }
    }

    void clearSelection() {
        if (!selection.isEmpty()) {
            selection.clear();
            mCallbacks.onSelectionUpdated(selection.size());
            GalleryFragmentAdapter.this.notifyDataChanged();
        }
    }
}